package com.hanxiaozhang.threadbase1ndedition.no5juccommonclass;

import java.util.concurrent.TimeUnit;
import java.util.concurrent.locks.LockSupport;

/**
 * 〈一句话功能简述〉<br>
 * 〈LockSupport〉
 * <p>
 * 概念：
 * 线程阻塞工具类
 * <p>
 * 常用方法：
 * blocker --> 负责此线程停放的同步对象
 * park(Object blocker)：通过"同步对象"暂停线程
 * parkNanos(Object blocker, long nanos)：通过"同步对象"暂停线程，不过有超时时间的限制
 * parkUntil(Object blocker, long deadline)：通过"同步对象"暂停线程，直到某个时间
 * park()：暂停当前线程
 * parkNanos(long nanos)：暂停当前线程，不过有超时时间的限制
 * parkUntil(long deadline)：暂停当前线程，直到某个时间
 * unpark(Thread thread)：恢复当前线程
 * getBlocker(Thread t)：获取线程的同步对象
 * <p>
 * 特点：
 * 1.park不需要获取某个对象的锁
 * 2.可以先调用unpark，然后调用park，结果是park不起作用，即可以说明park和unpark的使用不会出现死锁的情况
 * 3.中断的时候park不会抛出InterruptedException异常，所以需要在park之后自行判断中断状态，然后做额外的处理
 *
 * @author hanxinghua
 * @create 2021/11/14
 * @since 1.0.0
 */
public class No7LockSupport {

    public static void main(String[] args) {


        // order();

        handleInterrupt();

    }

    /**
     * 处理interrupt()
     */
    private static void handleInterrupt() {
        Thread t2 = new Thread(() -> {
            System.out.println("t2 开始执行");
            LockSupport.park();
            if (Thread.currentThread().isInterrupted()) {
                System.out.println("被中断了");
            }
            System.out.println("继续执行");
        });

        t2.start();
        t2.interrupt();
    }

    /**
     * park与unpark交换顺序
     */
    private static void order() {

        Thread t1 = new Thread(() -> {
            for (int i = 0; i < 10; i++) {
                System.out.println(i);
                if (i == 5) {
                    LockSupport.park();
                }
                try {
                    TimeUnit.SECONDS.sleep(1);
                } catch (InterruptedException e) {

                    e.printStackTrace();
                }
            }
        });

        t1.start();

        // i. 先调用unpark，然后调用park
        // LockSupport.unpark(t1);

        // ii. 先调用park，然后调用unpark
        try {
            TimeUnit.SECONDS.sleep(8);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        System.out.println("after 8 senconds!");
        LockSupport.unpark(t1);
    }
}
